package main

import (
	"fmt"
	"strconv"
)

func main() {
	var nodeStartNum string = "8000"
	var nodeNumber int = 15
	var maxConn int = 8
	var NodeMapping = make(map[string][]string)         // 存放节点之间映射关系
	var NodeAddrs []string = make([]string, nodeNumber) // 存放系统启动的节点 ip:port

	// 组织系统中存在的节点地址
	startNodeID, _ := strconv.Atoi(nodeStartNum)

	for i := 0; i < nodeNumber; i++ {
		nodeAddr := "localhost:" + strconv.Itoa(startNodeID+i)
		NodeAddrs[i] = nodeAddr
	}

	//// 节点映射关系[1个节点最多只连接8个节点]
	//for index, nodeAddr := range NodeAddrs {
	//	if maxConn > len(NodeAddrs[index:]) {
	//		// 拿到超出的索引数目
	//		tmp := maxConn - len(NodeAddrs[index:])
	//		//NodeMapping[nodeAddr] = append(NodeMapping[nodeAddr], NodeAddrs[index-tmp:index]...)
	//		NodeMapping[nodeAddr] = append(NodeMapping[nodeAddr], NodeAddrs[:tmp]...)
	//		NodeMapping[nodeAddr] = append(NodeMapping[nodeAddr], NodeAddrs[index:]...)
	//	} else {
	//		NodeMapping[nodeAddr] = append(NodeMapping[nodeAddr], NodeAddrs[index:index+maxConn]...)
	//	}
	//}
	//
	//fmt.Printf("%v\n", NodeMapping)

	//relation := nodeNumber / MaxConn

	for index, nodeAddr := range NodeAddrs {
		if index == 0 {
			continue
		}

		if index%maxConn == 0 {
			parentNode := NodeAddrs[index-1-(index-1)%maxConn] // 拿到上一轮的parentNode数目
			NodeMapping[parentNode] = append(NodeMapping[parentNode], nodeAddr)
			continue
		}

		// 求该节点的链接节点
		parentNode := NodeAddrs[index-index%maxConn]
		NodeMapping[parentNode] = append(NodeMapping[parentNode], nodeAddr)
	}

	for _, nodeAddr := range NodeAddrs {
		// 如果该节点没有分配网络映射
		if _, ok := NodeMapping[nodeAddr]; !ok {
			// 拿到该节点在网络映射中对应的键值
			var key string // 节点的键值
			for i, item := range NodeMapping {
				for _, j := range item {
					if j == nodeAddr {
						key = i
						break
					}
				}
			}

			NodeMapping[nodeAddr] = []string{key}
		}
	}

	for key, value := range NodeMapping {
		fmt.Println(key, value)
	}
}
